﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using CdcSoftware.Pivotal.Applications.Core.Client;
using CdcSoftware.Pivotal.Engine.UI.Forms;
using System.Data;
using System.Windows.Forms;
using CdcSoftware.Pivotal.Engine;
using CdcSoftware.Pivotal.Engine.Client.Services.Interfaces;
using CdcSoftware.Pivotal.Applications.Core.Common;

using CdcSoftware.Pivotal.Engine.Types.Searches;
using CdcSoftware.Pivotal.Engine.UI.DataTypes.Searches;
using CdcSoftware.Pivotal.Engine.Types.ServerTasks;
using CdcSoftware.Pivotal.Engine.Client.Types;
//using CdcSoftware.Pivotal.WindowsFormControls;
using System.ComponentModel;

namespace Pcm.Retail.Client.FormTasks
{
    public partial class RESales : FormClientTask
    {
        /// <summary>
        /// Form event.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="argsEA"></param>
        public virtual void OnKeyDownForm(PivotalControl sender, EventArgs argsEA)
        {
            try
            {
                KeyEventArgs args = argsEA as KeyEventArgs;

                if (Control.ModifierKeys == Keys.Shift && args.KeyCode == Keys.F1)
                    OnButtonClickExchange(sender, argsEA);
                else if (Control.ModifierKeys == Keys.Shift && args.KeyCode == Keys.F2)
                {
                    //DS: 19082013 - Retail Customer service group is not being used.
                    //if (Globals.CurrentUserInSecurityGroup("Retail Customer Service"))
                    RefundStub();
                }
                else if (Control.ModifierKeys == Keys.Shift && args.KeyCode == Keys.F3)
                    OnButtonClickNewSale(sender, argsEA);
                else if (Control.ModifierKeys == Keys.Shift && args.KeyCode == Keys.F4)
                    OnButtonClickVoidAndNew(sender, argsEA);
                else if (Control.ModifierKeys == Keys.Shift && args.KeyCode == Keys.F8)
                    OnButtonClickDeposit(sender, argsEA);
                else if (Control.ModifierKeys == Keys.Shift && args.KeyCode == Keys.F9)
                    OnButtonClickProcessTxn(sender, argsEA);
                else if (args.KeyCode == Keys.F11)
                {
                    this.FormControl.GetControlByDataName("RE_Product_Barcode").Focus();
                    OnButtonClickTender(sender, argsEA);
                }
                else if (args.KeyCode == Keys.F10)
                    OnButtonClickHold(sender, argsEA);
                else if (args.KeyCode == Keys.F9)
                    OnButtonClickCancel(sender, argsEA);
                else if (args.KeyCode == Keys.F8)
                    OnButtonClickMemberSearch(sender, argsEA);
                else if (args.KeyCode == Keys.F6)
                    OnButtonClickFetchHoldSales(sender, argsEA);
                else if (args.KeyCode == Keys.F4)
                    OnButtonClickTradeIn(sender, argsEA);
                else if (args.KeyCode == Keys.F3)
                    OnButtonClickRePrint(sender, argsEA);
                else if (args.KeyCode == Keys.F2)
                    OnButtonClickVoid(sender, argsEA);
                else if (args.KeyCode == Keys.F7)
                    this.FormView.LoadRecord();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On Enter press on field Membership ID move to the next field.
        /// </summary>
        /// <param name="sender">The control associated with the event triggered</param>
        /// <param name="args">The argument for the event</param>
        /// <history>
        /// #Revision   Date            Author      Description
        /// 6.0.9.1     2012-01-06      DS          Initial version for Retail.
        /// </history>
        public virtual void OnKeyEnterMemberID(object sender, KeyEventArgs args)
        {
            try
            {
                if (args.KeyCode == Keys.Enter)
                    this.FormControl.GetControlByDataName("RE_Staff_Code").Focus();
            }
            catch (Exception ex)
            {
                Globals.HandleException(ex, true);
            }
        }

        /// <summary>
        /// On Enter press on field Sales Rep Code to move to the next field.
        /// </summary>
        /// <param name="sender">The control associated with the event triggered</param>
        /// <param name="args">The argument for the event</param>
        /// <history>
        /// #Revision   Date            Author      Description
        /// 6.0.9.1     2012-01-06      DS          Initial version for Retail.
        /// </history>
        public virtual void OnKeyEnterSalesRepCode(object sender, KeyEventArgs args)
        {
            try
            {
                if (args.KeyCode == Keys.Enter)
                    this.FormControl.GetControlByDataName("RE_Customer_Type").Focus();
            }
            catch (Exception ex)
            {
                Globals.HandleException(ex, true);
            }
        }

        /// <summary>
        /// Barcode keyed in or populated after being scanned
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnDataSourceUpdatedBarCode(PivotalControl sender, EventArgs args)
        {
            try
            {
                bool productAdded = false;
                bool noProductFound = false;
                if (Convert.IsDBNull(this.PrimaryDataRow["RE_Product_Barcode"]))
                    return;

                DataTable product = Globals.GetDataTable("RE_Product for Barcode? Alt Code1? Alt Code2? Alt Code3?",
                        new object[] { this.PrimaryDataRow["RE_Product_Barcode"], this.PrimaryDataRow["RE_Product_Barcode"], 
                        this.PrimaryDataRow["RE_Product_Barcode"], this.PrimaryDataRow["RE_Product_Barcode"]}, "Product_Id", "RE_Serialized", "RE_Product_Type");

                if (String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Refund"))
                    PivotalMessageBox.Show("Products can't be added in a refund case." + Environment.NewLine +
                    "Please scan/enter the Source Receipt and delete the items not required to be refunded and proceed.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                else if (Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Order_Id"]) && String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Exchange"))
                    PivotalMessageBox.Show("Please scan/enter the Source Receipt before adding any product for Exchange.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                else if (product != null && product.Rows.Count == 1)
                {
                    if (InventoryCheck(1, false, product.Rows[0]["Product_Id"], null))
                    {
                        //Check whether it is a serialized item or not.
                        if (TypeConvert.ToBoolean(product.Rows[0]["RE_Serialized"]))
                        {
                            this.PrimaryDataRow["RE_Product_Id"] = product.Rows[0]["Product_Id"];
                            ((PivotalForeignKey)this.FormControl.GetControlByDataName("RE_Product_Serial_No_Id")).ReadOnly = false;
                            ((PivotalTextBox)this.FormControl.GetControlByDataName("RE_Serial_Number")).ReadOnly = false;
                            this.FormControl.GetControlByDataName("RE_Serial_Number").Focus();
                            return;
                        }
                        else
                        {
                            //Non-Serialized Item. Add the product directly to the grid.
                            this.PrimaryDataRow["RE_Product_Id"] = product.Rows[0]["Product_Id"];
                            if (AddProductToGrid(product, null))
                            {
                                this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                                productAdded = true;
                            }
                            //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. Else loop added.
                            else if(scannedPromotionProduct)
                                this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                        }
                    }
                }
                else if (product != null && product.Rows.Count > 1)
                {
                    PivotalMessageBox.Show("Multiple Product's found for the keyed in/scanned barcode: " +
                        TypeConvert.ToString(this.PrimaryDataRow["RE_Product_Barcode"]) + Environment.NewLine +
                        "Please contact the Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                    noProductFound = true;
                }
                else
                {
                    PivotalMessageBox.Show("No Product record found for the keyed in/scanned barcode.", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                    noProductFound = true;
                }
                this.PrimaryDataRow["RE_Serial_Number"] = DBNull.Value;
                this.PrimaryDataRow["RE_Product_Serial_No_Id"] = DBNull.Value;
                this.PrimaryDataRow["RE_Product_Barcode"] = DBNull.Value;
                //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. Added additional check for scannedPromotionProduct.
                if (productAdded || noProductFound || scannedPromotionProduct)
                    this.FormControl.GetControlByName("REProductBarcode").Focus();
                else if (String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Refund") ||
                    (Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Order_Id"]) && String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Exchange")))
                    this.FormControl.GetControlByDataName("RE_Source_Receipt_No").Focus();
                else
                    this.FormControl.GetControlByDataName("RE_Product_Id").Focus();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Barcode keyed in or populated after being scanned
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0    28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnKeyDownBarCode(PivotalControl sender, KeyEventArgs args)
        {
            try
            {
                if (args.KeyCode == Keys.Enter)
                    this.FormControl.GetControlByDataName("RE_Receipt_Number").Focus();//Don't worry abt the focus as it gets set again. This is just to naturally fire the datasourceupdated event.
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Barcode keyed in or populated after being scanned
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnKeyDownSerialNumber(PivotalControl sender, KeyEventArgs args)
        {
            try
            {
                if (args.KeyCode == Keys.Enter)
                    this.FormControl.GetControlByDataName("RE_Receipt_Number").Focus();//Don't worry abt the focus as it gets set again. This is just to naturally fire the datasourceupdated event.
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On change of Customer_Type field.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.9.1    25-11-2011  DS      Initial Version for Retail
        /// </history>
        public virtual void OnDataSourceUpdatedCustomerType(object sender, EventArgs args)
        {
            try
            {
                SetVisibilityOfSections();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On change of Product Serial Number field 
        /// </summary>
        /// <param name="sender">PivotalControl</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnDataSourceUpdatedSerialNumberText(PivotalControl sender, EventArgs args)
        {
            try
            {
                bool productAdded = false;
                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Serial_Number"]) && !Convert.IsDBNull(this.PrimaryDataRow["RE_Product_Id"]))
                {
                    //Check for Inventory. No Inventory, do not allow to add products. 
                    DataTable inventory = Globals.GetDataTable("RE_Inventory for Product? At current Store",
                        new object[] { this.PrimaryDataRow["RE_Product_Id"] }, "Product_Id", "Quantity_Actual");

                    if (inventory != null && inventory.Rows.Count > 0 && TypeConvert.ToInt16(inventory.Rows[0]["Quantity_Actual"]) >= 1)
                    {
                        DataTable productSerialNo = Globals.GetDataTable("RE_Product Serial No for Product? Serial_Number? Current Store",
                            new object[] { this.PrimaryDataRow["RE_Product_Id"], this.PrimaryDataRow["RE_Serial_Number"] }, "RE_Product_Serial_No_Id",
                            "Serial_Number", "Product_Id", "Available_For_Sale", "Voucher", "Voucher_Status");

                        if (productSerialNo != null && productSerialNo.Rows.Count > 0)
                        {
                            if (AddProductToGrid(null, productSerialNo))
                            {
                                this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                                productAdded = true;
                            }
                            //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. Else loop added.
                            else if (scannedPromotionProduct)
                                this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                        }
                        else
                            PivotalMessageBox.Show("No product found for the keyed in/scanned Serial Number.", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                    }
                    else
                        PivotalMessageBox.Show("No stock found for the keyed in/scanned barcode.", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);

                    this.PrimaryDataRow["RE_Serial_Number"] = DBNull.Value;
                    //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. scannedPromotionProduct check added.
                    if (productAdded || scannedPromotionProduct)
                    {
                        this.PrimaryDataRow["RE_Product_Barcode"] = DBNull.Value;
                        ((PivotalTextBox)this.FormControl.GetControlByDataName("RE_Serial_Number")).ReadOnly = true;
                        ((PivotalForeignKey)this.FormControl.GetControlByDataName("RE_Product_Serial_No_Id")).ReadOnly = true;
                        this.FormControl.GetControlByDataName("RE_Product_Barcode").Focus();
                        //Promotion Selection.
                        //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. scannedPromotionProduct check added.
                        if (this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count > 0 && !scannedPromotionProduct)
                            ConfigurePromotion(this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows[this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count - 1]);
                    }
                    else
                        this.FormControl.GetControlByDataName("RE_Serial_Number").Focus();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
            finally
            {
                Globals.SelectedPromotions = null;
            }
        }

        /// <summary>
        /// On change of Product Serial Number dropdown field 
        /// </summary>
        /// <param name="sender">PivotalControl</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnDataSourceUpdatedSerialNumberDropDown(PivotalControl sender, EventArgs args)
        {
            try
            {
                bool productAdded = false;
                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Product_Serial_No_Id"]) && !Convert.IsDBNull(this.PrimaryDataRow["RE_Product_Id"]))
                {
                    DataTable productSerialNo = Globals.GetDataTable("RE_Product Serial No for Product? Serial_Number? Current Store",
                        new object[] { this.PrimaryDataRow["RE_Product_Id"], this.PrimaryDataRow["RE_Product_Serial_No_Id__Seria"] },
                        "RE_Product_Serial_No_Id", "Serial_Number", "Product_Id", "Available_For_Sale", "Voucher", "Voucher_Status");

                    if (productSerialNo != null && productSerialNo.Rows.Count > 0)
                    {
                        if (AddProductToGrid(null, productSerialNo))
                        {
                            this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                            productAdded = true;
                        }
                        //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. Else loop added.
                        else if (scannedPromotionProduct)
                            this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                    }
                    else
                        PivotalMessageBox.Show("No product found for the selected Serial Number.", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);

                    this.PrimaryDataRow["RE_Serial_Number"] = DBNull.Value;
                    this.PrimaryDataRow["RE_Product_Serial_No_Id"] = DBNull.Value;
                    //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. scannedPromotionProduct check added.
                    if (productAdded || scannedPromotionProduct)
                    {
                        this.PrimaryDataRow["RE_Product_Barcode"] = DBNull.Value;
                        ((PivotalTextBox)this.FormControl.GetControlByDataName("RE_Serial_Number")).ReadOnly = true;
                        ((PivotalForeignKey)this.FormControl.GetControlByDataName("RE_Product_Serial_No_Id")).ReadOnly = true;
                        this.FormControl.GetControlByName("REProductBarcode").Focus();
                        //Promotion Selection.
                        //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. scannedPromotionProduct check added.
                        if (this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count > 0 && !scannedPromotionProduct)
                            ConfigurePromotion(this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows[this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count - 1]);
                    }
                    else
                        this.FormControl.GetControlByDataName("RE_Product_Serial_No_Id").Focus();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
            finally
            {
                Globals.SelectedPromotions = null;
            }
        }

        /// <summary>
        /// Open the Tender form on Tender button click or pressing F12
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickTender(PivotalControl sender, EventArgs args)
        {
            try
            {
                string message = string.Empty;
                DataTable cashierLog = null;

                if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) != "Processed" &&
                    TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) != "Void")
                {
                    cashierLog = Globals.GetDataTable("RE_All Cashier Logins for Today where EndTime is Null with POS ?",
                            new object[] { this.PrimaryDataRow["RE_POS_Id"] }, "Staff_Id", "Store_Id", "POS_Id", "Batch_Id");

                    if (Globals.CurrentUserInSecurityGroup("Retail Customer Service") || Globals.CurrentUserInSecurityGroup("Retail POS"))
                    {
                        if (cashierLog != null && cashierLog.Rows.Count == 0)
                        {
                            PivotalMessageBox.Show("No Cashier found logged in to the POS.", MessageBoxButtons.OK, MessageBoxIcon.Warning);
                            this.FormView.CloseForm(true);
                            Globals.NewForm("RE_Cashier_Log", null);
                            return;
                        }
                        else if (cashierLog != null && cashierLog.Rows.Count > 1)
                        {
                            PivotalMessageBox.Show("Multiple Cashiers are found logged in to the POS. Please contact the Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                            return;
                        }
                    }
                }

                if (!this.FormView.VerifyRecord(out message) || !this.FormView.ValidateRequiredFields(out message))
                {
                    PivotalMessageBox.Show("Unable to save the form data. Provide a value for all required fields.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    return;
                }

                if (this.RecordId != null)
                {
                    if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) == "Processed" ||
                        TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) == "Void")
                    {
                        Globals.ShowModalForm("RE_Tender", this.RecordId, null);
                        return;
                    }
                    else
                    {
                        //One Cashier logged in
                        if (cashierLog != null && cashierLog.Rows.Count == 1)
                        {
                            //Check for Current batch != Batch for existing sale
                            if (!Globals.EqualValues(Id.Create(this.PrimaryDataRow["RE_Batch_Id"]), Id.Create(cashierLog.Rows[0]["Batch_Id"])))
                            {
                                PivotalMessageBox.Show("The sale you wish to process does not belong to the current batch.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                return;
                            }
                            else
                            {
                                this.PrimaryDataRow["RE_Cashier_Id"] = cashierLog.Rows[0]["Staff_Id"];
                                this.PrimaryDataRow["RE_POS_Id"] = cashierLog.Rows[0]["POS_Id"];
                                this.PrimaryDataRow["Account_Manager_Id"] = TypeConvert.ToDBValue(this.SystemClient.UserProfile.EmployeeId);
                            }
                        }
                    }
                }

                //For Type = Exchange, 
                //Since Exchange reason is mandatory, so before opening the Tender form check if the value is entered
                if (TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Exchange")
                {
                    //If no -ve quantities are entered then, prompt the user to enter one -ve quantity for Exchange
                    if (this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].AsEnumerable().Count(a => TypeConvert.ToInt32(a["Quantity"]) >= 0)
                        == this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count)
                    {
                        PivotalMessageBox.Show("Quantity should be negative for at least one row for Exchange transaction.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return;
                    }
                    //If no +ve quantities are entered then, prompt the user to enter one +ve quantity for Exchange
                    if (this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].AsEnumerable().Count(a => TypeConvert.ToInt32(a["Quantity"]) < 0)
                        == this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count)
                    {
                        PivotalMessageBox.Show("Quantity should be positive for at least one row for Exchange transaction.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return;
                    }
                    //make sure user enters exchange reason for -ve quantities
                    if (this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].AsEnumerable().Where(a => TypeConvert.ToInt32(a["Quantity"]) < 0).
                        Count(a => TypeConvert.ToString(a["RE_Exchange_Reason"]) == string.Empty) > 0)
                    {
                        PivotalMessageBox.Show("Please Enter Exchange Reason for negative quantities.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return;
                    }
                }
                //For Type = Refund, 
                //Since Refund reason is mandatory, so before opening the Tender form check if the value is entered
                else if (TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Refund")
                {
                    //make sure user enters refund reason for -ve quantities
                    if (this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].AsEnumerable().Where(a => TypeConvert.ToInt32(a["Quantity"]) < 0).
                        Count(a => TypeConvert.ToString(a["RE_Refund_Reason"]) == string.Empty) > 0)
                    {
                        PivotalMessageBox.Show("Please Enter Refund Reason.", MessageBoxButtons.OK, MessageBoxIcon.Warning);
                        return;
                    }
                }
                //For Deposit converted to Sale, check for the amounts.
                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Sale_Deposit_Link_Id"]))
                {
                    double depositAmt = TypeConvert.ToDouble(Globals.SqlIndex("SFA_Order", "Quote_Total", Id.Create(this.PrimaryDataRow["RE_Sale_Deposit_Link_Id"])));
                    if (TypeConvert.ToDouble(this.PrimaryDataRow["Quote_Total"]) > depositAmt)
                    {
                        PivotalMessageBox.Show("Sale Amount($" + this.PrimaryDataRow["Quote_Total"] + ") can't be more than the Deposit Amount($" + depositAmt + 
                            ")." + Environment.NewLine + "Please select a different product.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                        return;
                    }
                }

                DataTable orderProduct = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                //Check if all the items are scanned or not. Do not allow to move to Tender screen if all the items are not scanned including those from Promotion.
                if (orderProduct.AsEnumerable().Where(a => TypeConvert.ToBoolean(a["RE_Item_Scanned"])).Count() != orderProduct.Rows.Count)
                {
                    PivotalMessageBox.Show("Please scan the Promotion items before moving to Tender.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                    return;
                }                

                //NN 16082013: Getting the count of Actual Promotion Items added.
                int productWithTypePromotion = (from DataRow myRow in orderProduct.Rows
                                                where TypeConvert.ToString(myRow["RE_Product_Type"]) == "Promotion"
                                                select Id.Create(myRow["RE_Promotion_Id"])).Count();

                //NN 16082013: Comparing the promotionsCount(Promotions items which are supposed to be added) with productWithTypePromotion(Actual Promotion items added).
                //If both the count dont match then raise an error prompt.
                if (promotionsCount != productWithTypePromotion)
                {
                    PivotalMessageBox.Show("There was some error while configuring Promotions." + Environment.NewLine + 
                                            "Please create a new Sale.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                    return;
                }

                if (orderProduct != null && orderProduct.Rows.Count > 0)
                {
                    //No such case where DC can be a Voucher.
                    ////Before moving to Tender check if for any discount condition is Voucher. If so ask the user to input the Voucher Number.
                    //foreach (DataRow dr in orderProduct.Rows)
                    //{
                    //    if (TypeConvert.ToBoolean(dr["RE_Discount_Condition1_Id__Vou"]) && Convert.IsDBNull(dr["RE_Voucher_Number"]))
                    //    {
                    //        PivotalMessageBox.Show("You have selected Discount which requires a Voucher Number." + Environment.NewLine +
                    //        "Please enter a Voucher Number corresponding to the row where Voucher? is checked before proceeding to Tender screen.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    //        return;
                    //    }
                    //}

                    //DS: 27092013 - Double check the CommonField Update and Total Section Update as in case there was some connectivity related problem, 
                    //the finance details should not provide wrong information. Also need to make sure that the flow must not go through in case of any discrepency.
                    int qty = 0;
                    foreach (DataRow dr in orderProduct.Rows)
                    {
                        CommonFieldPopulate(dr);
                        qty = qty + TypeConvert.ToInt16(dr["Quantity"]);
                    }
                    TotalsSectionCalculations();

                    if (TypeConvert.ToInt16(this.PrimaryDataRow["RE_Total_Qty"]) != qty)
                    {
                        PivotalMessageBox.Show("There was some error while adding the Products." + Environment.NewLine +
                                            "Please create a new Sale.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                        return;
                    }

                    //For the sales which is not processed set the status to Pending.
                    this.PrimaryDataRow["RE_Order_Status"] = "Pending";

                    if (!this.FormView.SaveRecord())
                        return;
                    else
                    {
                        DataTable authorzn = this.FormData.DataSet.Tables["RE_Authorization_Order_Id"];
                        if (string.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Exchange") ||
                            string.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Refund"))
                        {
                            var results = from myRow in authorzn.AsEnumerable()
                                          where myRow.Field<string>("Event") == TypeConvert.ToString(this.PrimaryDataRow["RE_Type"])
                                          select myRow;
                            if (results.Count() == 0)
                            {
                                //Create a new Authorization row.
                                base.NewSecondaryRecord("RE_Authorization_Order_Id");
                                authorzn.Rows[authorzn.Rows.Count - 1]["Authorized"] = DBNull.Value;
                                authorzn.Rows[authorzn.Rows.Count - 1]["RE_Authorized_By_Id"] = DBNull.Value;
                                authorzn.Rows[authorzn.Rows.Count - 1]["Event"] = TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]);
                                this.FormView.SaveRecord();
                                this.ShowReAuthorizationForm(true);
                                //DS: 17052013 - Load the record post authorization.
                                this.FormView.LoadRecord();
                                //DS: 12052013 - Was loosing the color Coding.
                                HighlightRows();
                                return;
                            }
                        }

                        if (this.DataSet.Tables["RE_Authorization_Order_Id"].AsEnumerable().Count(a => TypeConvert.ToBoolean(a["Authorized"]))
                            != this.DataSet.Tables["RE_Authorization_Order_Id"].Rows.Count)
                        {
                            this.ShowReAuthorizationForm(true);
                            //DS: 17052013 - Load the record post authorization.
                            this.FormView.LoadRecord();
                            //DS: 12052013 - Was loosing the color Coding.                             
                            HighlightRows();
                            return;
                        }

                        //Pass on the Used quantity for the Bday promotion to update for the contact record in the table RE_Member_Bday_Disc_Quota.
                        if (!Convert.IsDBNull(this.PrimaryDataRow["Member_Bday_Discount_Id"]) && bDayQuota != null)
                        {
                            int quantityWithBdayDisc = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].AsEnumerable().Where(a => Id.Create(a["RE_Discount_Condition1_Id"])
                                == Id.Create(this.PrimaryDataRow["Member_Bday_Discount_Id"])).Sum(a => TypeConvert.ToInt32(a["Quantity"]));
                            if (quantityWithBdayDisc != 0)
                                this.TransitionPointParameter.SetUserDefinedParameter(2, quantityWithBdayDisc);
                        }

                        Globals.ShowModalForm("RE_Tender", this.RecordId, this.TransitionPointParameter.ParameterList);
                        
                        //Checking the value of Global Variable.If it is set to TRUE then this Sales record is already deleted from Tender Form
                        //Therfore Closing current form
                        if (Globals.SalesRecordDeleted)
                        {
                            this.FormView.CloseForm(true);
                            //Setting the value back to false after closing current form.
                            Globals.SalesRecordDeleted = false;
                            return;
                        }

                        //refresh the button to show processed if any changes are made
                        this.FormView.LoadRecord();
                        HighlightRows();

                        if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) == "Processed")
                        {
                            bool cashierAutoLogout = TypeConvert.ToBoolean(this.PrimaryDataRow["RE_LOB_Id__Auto_Logout_Cashier"]);
                            string status = TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]);

                            //The sale is tendered. Close the old sale and open a new sale.
                            this.FormView.CloseForm(true);

                            if (cashierAutoLogout)
                            {
                                //Auto Logout the Cashier as it is defined at the LOB Level.
                                //Clock out the cashier clocked in. For the POS the cashier was logged-in, nullify the value for Cashier_Id.
                                this.SystemClient.ExecuteServerTask("RE_Sale", "CashierAutoLogout", new Type[] { typeof(object) },
                                    new object[] { this.PrimaryDataRow["RE_POS_Id"] });

                                //Set the bottom status strip text.
                                Globals.SetCashierStatusStrip(Globals.StatusStripPane.EnvironmentPane);

                                //Globals.RunCommand("RE.AS.POS_Home", null);
                                OpenActiveSearchPage("POS Home");
                                return;
                            }

                            //Refund is carried out by the Cashier only
                            //if (string.Equals(status.ToUpper(), "REFUND"))
                            //{
                            //    //Globals.RunCommand("RE.AS.Customer_Service", null);
                            //    OpenActiveSearchPage("Customer Service Home");
                            //    return;
                            //}
                            Globals.NewForm("RE_Sale – Walk In", null, ActionTargetWindow.Current);
                        }
                    }
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// Set Set the status to Hold. Save the form and show a New Sale form
        /// button click or pressing F10
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickHold(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 06082013 - When the Sale is Processed, the Hold functionality should be locked down.
                if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) != "Processed" && TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) != "Void")
                {
                    //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                    if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                        PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    else
                    {
                        DataTable orderProduct = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                        if (orderProduct != null && orderProduct.Rows.Count > 0)
                        {
                            int productWithTypePromotion = (from DataRow myRow in orderProduct.Rows
                                                            where TypeConvert.ToString(myRow["RE_Product_Type"]) == "Promotion"
                                                            select Id.Create(myRow["RE_Promotion_Id"])).Count();

                            //NN 16082013: Comparing the promotionsCount(Promotions items which are supposed to be added) with productWithTypePromotion(Actual Promotion items added).
                            //If both the count dont match then raise an error prompt.
                            if (promotionsCount != productWithTypePromotion)
                            {
                                PivotalMessageBox.Show("There was some error while configuring Promotions." + Environment.NewLine +
                                                        "Please create a new Sale.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                                return;
                            }

                            this.PrimaryDataRow["RE_Order_Status"] = "Hold";
                            if (this.FormView.SaveRecord())
                            {
                                this.FormView.CloseForm(true);
                                Globals.NewForm("RE_Sale – Walk In", null, ActionTargetWindow.Current);
                            }
                        }
                    }
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On click of Reprint button.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.9.1    28-11-2011  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickRePrint(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                {
                    if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) == "Processed")
                    {
                        base.NewSecondaryRecord("RE_Authorization_Order_Id");
                        DataTable authorzn = this.FormData.DataSet.Tables["RE_Authorization_Order_Id"];
                        authorzn.Rows[authorzn.Rows.Count - 1]["Authorized"] = DBNull.Value;
                        authorzn.Rows[authorzn.Rows.Count - 1]["RE_Authorized_By_Id"] = DBNull.Value;
                        authorzn.Rows[authorzn.Rows.Count - 1]["Event"] = "Reprint Reciept.";

                        if (this.FormView.SaveRecord())
                        {
                            this.TransitionPointParameter.SetUserDefinedParameter(7, false);
                            //Show the Authorization Prompt.
                            this.ShowReAuthorizationForm(false);
                            this.LoadRecord();

                            if (this.DataSet.Tables["RE_Authorization_Order_Id"].AsEnumerable().Count(a => TypeConvert.ToBoolean(a["Authorized"]) == true)
                                        == this.DataSet.Tables["RE_Authorization_Order_Id"].Rows.Count)
                            {
                                //Reprint the receipt.
                                this.TransitionPointParameter.SetUserDefinedParameter(4, "REPRINT");
                                Globals.ShowModalForm("RE_Tender", this.RecordId, this.TransitionPointParameter.ParameterList);
                            }
                            else
                                PivotalMessageBox.Show("Please authorize the Re-Print receipt.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                        }
                    }
                    else
                        PivotalMessageBox.Show("Reprinting is possible only for orders which are Processed.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// On click of Void button.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.9.1    28-11-2011  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickVoid(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                    VoidSale();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// Cancel the sale and open a new sale
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickNewSale(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available in Offline mode.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                {
                    if (this.FormView.Dirty)
                    {
                        if (PivotalMessageBox.Show("Changes to 'New Sale' will be lost if you navigate away." + Environment.NewLine +
                        "Click OK to continue, or Cancel to stay on the current record.", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) == DialogResult.OK)
                        {
                            this.FormView.CloseForm(true);
                            Globals.NewForm("RE_Sale – Walk In", null, ActionTargetWindow.Current);
                        }
                        else
                            return;
                    }
                    else
                    {
                        this.FormView.CloseForm(true);
                        Globals.NewForm("RE_Sale – Walk In", null, ActionTargetWindow.Current);
                    }
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Cancel the sale and open a new sale of type Exchange
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickExchange(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                {
                    if (this.FormView.Dirty)
                    {
                        if (PivotalMessageBox.Show("You will lose unsaved changes to the form." + Environment.NewLine +
                            "Are you sure to navigate away from the current form?", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) == DialogResult.OK)
                            OpenExchangeSale();
                        else
                            return;
                    }
                    else
                        OpenExchangeSale();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Opens a new sale of type Deposit.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickDeposit(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                {
                    if (this.FormView.Dirty)
                    {
                        if (PivotalMessageBox.Show("You will lose unsaved changes to the form." + Environment.NewLine +
                            "Are you sure to navigate away from the current form?", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) == DialogResult.OK)
                            OpenDepositSale();
                        else
                            return;
                    }
                    else
                        OpenDepositSale();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Opens a new sale of type Trade-In.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickTradeIn(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                {
                    if (this.FormView.Dirty)
                    {
                        if (PivotalMessageBox.Show("You will lose unsaved changes to the form." + Environment.NewLine +
                            "Are you sure to navigate away from the current form?", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) == DialogResult.OK)
                            OpenTradeInSale();
                        else
                            return;
                    }
                    else
                        OpenTradeInSale();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Void a sale and Open a new Sale with the same products.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickVoidAndNew(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                {
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    return;
                }
                //Check for Cashier Login before creating a new sale.
                DataTable cashierLog = Globals.GetDataTable("RE_All Cashier Logins for Today where EndTime is Null with POS ?",
                            new object[] { this.PrimaryDataRow["RE_POS_Id"] }, "Staff_Id", "Store_Id", "POS_Id", "Batch_Id");

                if (Globals.CurrentUserInSecurityGroup("Retail Customer Service") || Globals.CurrentUserInSecurityGroup("Retail POS"))
                {
                    if (cashierLog != null && cashierLog.Rows.Count == 0)
                    {
                        PivotalMessageBox.Show("No Cashier found logged in to the POS.", MessageBoxButtons.OK, MessageBoxIcon.Warning);
                        this.FormView.CloseForm(true);
                        Globals.NewForm("RE_Cashier_Log", null);
                        return;
                    }
                    else if (cashierLog != null && cashierLog.Rows.Count > 1)
                    {
                        PivotalMessageBox.Show("Multiple Cashiers are found logged in to the POS. Please contact the Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                        return;
                    }

                    //DS: 19082013 - No need to check for Dirty flag as "Processed Sale" will always be in read-only mode.
                    ////Check for Cashier Login before doing any operation.
                    //if (this.FormView.Dirty)
                    //{
                    //    if (PivotalMessageBox.Show("You will lose unsaved changes to the form." + Environment.NewLine +
                    //        "Are you sure to navigate away from the current form?", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) != DialogResult.OK)
                    //        return;
                    //}
                    if (VoidSale())
                    {
                        //Create a new sale with the same products as the opened one and directly open the Tender form.
                        object newOrder = this.SystemClient.ExecuteServerTask("RE_Sale", "CreateNewSaleForVoidnNew", new Type[] { typeof(Id), typeof(object), typeof(object) },
                                            new object[] { this.RecordId, this.PrimaryDataRow["RE_Cashier_Id"], this.PrimaryDataRow["RE_POS_Id"] });

                        //Open Tender for the new Order created.
                        if (newOrder != null)
                        {
                            Globals.ShowModalForm("RE_Tender", Id.Create(newOrder), null);

                            //Checking the value of Global Variable.If it is set to TRUE then this Sales record is already deleted from Tender Form
                            //Therfore Closing current form
                            if (Globals.SalesRecordDeleted)
                            {
                                this.FormView.CloseForm(true);
                                //Setting the value back to false after closing current form.
                                Globals.SalesRecordDeleted = false;
                                return;
                            }

                            //refresh the button to show processed if any changes are made
                            Globals.ShowForm("RE_Sale – Walk In", Id.Create(newOrder), null, ActionTargetWindow.Current);

                            if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) == "Processed")
                            {
                                bool cashierAutoLogout = TypeConvert.ToBoolean(this.PrimaryDataRow["RE_LOB_Id__Auto_Logout_Cashier"]);
                                string status = TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]);

                                //The sale is tendered. Close the old sale and open a new sale.
                                this.FormView.CloseForm(true);

                                if (cashierAutoLogout)
                                {
                                    //Auto Logout the Cashier as it is defined at the LOB Level.
                                    //Clock out the cashier clocked in. For the POS the cashier was logged-in, nullify the value for Cashier_Id.
                                    this.SystemClient.ExecuteServerTask("RE_Sale", "CashierAutoLogout", new Type[] { typeof(object) },
                                        new object[] { this.PrimaryDataRow["RE_POS_Id"] });

                                    //Set the bottom status strip text.
                                    Globals.SetCashierStatusStrip(Globals.StatusStripPane.EnvironmentPane);

                                    //Globals.RunCommand("RE.AS.POS_Home", null);
                                    OpenActiveSearchPage("POS Home");
                                    return;
                                }

                                if (string.Equals(status.ToUpper(), "REFUND"))
                                {
                                    //Globals.RunCommand("RE.AS.Customer_Service", null);
                                    OpenActiveSearchPage("Customer Service Home");
                                    return;
                                }
                                Globals.NewForm("RE_Sale – Walk In", null, ActionTargetWindow.Current);
                            }
                        }
                    }
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Cancel the sale and open a new sale of type Refund
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1    01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickRefund(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                    RefundStub();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Add a new row for Deposit
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1    01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickDepositItem(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (SaveRecord())
                {
                    DataTable depositProduct = Globals.GetDataTable("RE_Products with Type as Deposit", null, new string[] { "Product_Id" });
                    if (depositProduct != null && depositProduct.Rows.Count > 0)
                    {
                        TransitionPointParameter transParam = new TransitionPointParameter();
                        ParameterList param = new ParameterList();
                        transParam.Construct();
                        transParam.AddDefaultColumn("SFA_Order_Id", this.RecordId);
                        transParam.AddDefaultColumn("Product_Id", depositProduct.Rows[0]["Product_Id"]);
                        transParam.AddDefaultColumn("Quantity", 1);
                        transParam.AddDefaultColumn("RE_Product_Type", "Deposit");

                        if (this.PrimaryDataRow["RE_Staff_Code"] != DBNull.Value)
                        {
                            transParam.AddDefaultColumn("RE_Staff_Code", this.PrimaryDataRow["RE_Staff_Code"]);
                            transParam.AddDefaultColumn("RE_Staff_Id", this.PrimaryDataRow["RE_Staff_Id"]);
                        }

                        transParam.SetUserDefinedParameter(1, true);
                        transParam.CopyToParameterList(param);
                        Globals.ShowForm("RE_AddOrderProductItem", null, param, ActionTargetWindow.Modal);

                        this.LoadRecord();
                        this.OnFormReloaded();
                        DataTable orderProducts = this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                        if (orderProducts.Rows.Count > 0 && string.Equals(TypeConvert.ToString(orderProducts.Rows[orderProducts.Rows.Count - 1]["RE_Product_Type"]), "Deposit"))
                        {
                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "Quantity", orderProducts.Rows.Count - 1, false);
                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Promotion_Id", orderProducts.Rows.Count - 1, false);
                            CommonFieldPopulate(orderProducts.Rows[orderProducts.Rows.Count - 1]);
                            TotalsSectionCalculations();
                        }
                    }
                    else
                        PivotalMessageBox.Show("Deposit Item is not configured." + Environment.NewLine + "Please contact System Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Add a new row for Fees for IPP
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1    01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickFeesItem(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (SaveRecord())
                {
                    DataTable feesProduct = Globals.GetDataTable("RE_Products with Type as Fees", null, new string[] { "Product_Id" });
                    if (feesProduct != null && feesProduct.Rows.Count > 0)
                    {
                        TransitionPointParameter transParam = new TransitionPointParameter();
                        ParameterList param = new ParameterList();
                        transParam.Construct();
                        transParam.AddDefaultColumn("SFA_Order_Id", this.RecordId);
                        transParam.AddDefaultColumn("Product_Id", feesProduct.Rows[0]["Product_Id"]);
                        transParam.AddDefaultColumn("Quantity", 1);
                        transParam.AddDefaultColumn("RE_Product_Type", "Fees for IPP");
                        if (this.PrimaryDataRow["RE_Staff_Code"] != DBNull.Value)
                        {
                            transParam.AddDefaultColumn("RE_Staff_Code", this.PrimaryDataRow["RE_Staff_Code"]);
                            transParam.AddDefaultColumn("RE_Staff_Id", this.PrimaryDataRow["RE_Staff_Id"]);
                        }
                        transParam.SetUserDefinedParameter(1, null);
                        transParam.CopyToParameterList(param);
                        Globals.ShowModalForm("RE_AddOrderProductItem", null, param);

                        this.LoadRecord();
                        this.OnFormReloaded();
                        HighlightRows();
                        DataTable orderProducts = this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                        if (orderProducts.Rows.Count > 0 && string.Equals(TypeConvert.ToString(orderProducts.Rows[orderProducts.Rows.Count - 1]["RE_Product_Type"]), "Fees for IPP"))
                        {
                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "Quantity", orderProducts.Rows.Count - 1, false);
                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Promotion_Id", orderProducts.Rows.Count - 1, false);
                            CommonFieldPopulate(orderProducts.Rows[orderProducts.Rows.Count - 1]);
                            TotalsSectionCalculations();
                        }
                    }
                    else
                        PivotalMessageBox.Show("Fees Item is not configured." + Environment.NewLine + "Please contact System Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Add a new row for Trade-In
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1   01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickTradeInItem(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (SaveRecord())
                {
                    DataTable tradeInProduct = Globals.GetDataTable("RE_Products with Type as Trade-In", null, new string[] { "Product_Id" });
                    if (tradeInProduct != null && tradeInProduct.Rows.Count > 0)
                    {
                        TransitionPointParameter transParam = new TransitionPointParameter();
                        ParameterList param = new ParameterList();
                        transParam.Construct();
                        transParam.AddDefaultColumn("SFA_Order_Id", this.RecordId);
                        transParam.AddDefaultColumn("Product_Id", tradeInProduct.Rows[0]["Product_Id"]);
                        transParam.AddDefaultColumn("Quantity", -1);
                        transParam.AddDefaultColumn("RE_Product_Type", "Trade-In");
                        if (this.PrimaryDataRow["RE_Staff_Code"] != DBNull.Value)
                        {
                            transParam.AddDefaultColumn("RE_Staff_Code", this.PrimaryDataRow["RE_Staff_Code"]);
                            transParam.AddDefaultColumn("RE_Staff_Id", this.PrimaryDataRow["RE_Staff_Id"]);
                        }
                        transParam.SetUserDefinedParameter(1, false);
                        transParam.CopyToParameterList(param);
                        Globals.ShowModalForm("RE_AddOrderProductItem", null, param);

                        this.LoadRecord();
                        HighlightRows();
                        DataTable orderProducts = this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                        if (orderProducts.Rows.Count > 0 && string.Equals(TypeConvert.ToString(orderProducts.Rows[orderProducts.Rows.Count - 1]["RE_Product_Type"]), "Trade-In"))
                        {
                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "Quantity", orderProducts.Rows.Count - 1, false);
                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Promotion_Id", orderProducts.Rows.Count - 1, false);
                            CommonFieldPopulate(orderProducts.Rows[orderProducts.Rows.Count - 1]);
                            TotalsSectionCalculations();
                        }
                    }
                    else
                        PivotalMessageBox.Show("Trade-In Item is not configured." + Environment.NewLine + "Please contact System Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On hit of Cancel button
        /// This will Delete the record on Cancel Click.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickCancel(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 06082013 - When the Sale is Processed, the Hold functionality should be locked down.
                if (this.RecordId != null && TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) != "Processed" 
                    && TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) != "Void")
                {
                    //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                    if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                        PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    else
                    {
                        //If Hold Transaction is Cancelled,New Sales form should open
                        bool openNewSales = (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]).ToUpper() == "HOLD" ? true : false);

                        if (PivotalMessageBox.Show("Are you sure you want to delete this record?",
                            MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) == DialogResult.OK)
                        {
                            this.DeleteRecord();
                            this.FormView.CloseForm(true);

                            //If Hold Transaction is Cancelled,New Sales form should open
                            if (openNewSales)
                                Globals.NewForm("RE_Sale – Walk In", null, ActionTargetWindow.Current);
                        }
                    }
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Retrieve the Transactions which were put on “Hold”.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickFetchHoldSales(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                {
                    DataTable holdSales = Globals.GetDataTable("RE_All Orders with Status as Hold and Batch?", new object[] { this.PrimaryDataRow["RE_Batch_Id"] }, "RE_Type");
                    if (holdSales != null && holdSales.Rows.Count > 0)
                    {
                        Id orderId = Globals.ShowSingleSelectionList(holdSales, "Select an Order from the List below.", String.Empty);

                        if (orderId != null)
                        {
                            this.FormView.CloseForm(true);
                            Globals.ShowForm("RE_Sale – Walk In", orderId);
                        }
                    }
                    else
                        PivotalMessageBox.Show("There are no Orders in status Hold for this Batch.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Cancel the sale and open a new sale
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// 6.0.9.1    01/09/2012  DS      When the form was not dirty, the button was useless.
        /// </history>
        public virtual void OnButtonClickSalesSearch(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (this.FormView.Dirty)
                {
                    if (PivotalMessageBox.Show("Changes to 'Sale:" + this.PrimaryDataRow["Rn_Descriptor"].ToString()
                        + "' will be lost if you exit. Click OK to exit, or Cancel to stay on the current record.", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning)
                        != DialogResult.OK)
                        return;
                }

                this.FormView.CloseForm(false);
                IActionService actionService = ClientContext.ClientAPIService.GetService<IActionService>();
                Command command = Globals.SystemClient.UserProfile.GetMetaItem<Command>("RE.NewSearch.Sale");
                IAction action = actionService.CreateAction(command);
                action.TargetWindow = ActionTargetWindow.Current;
                actionService.ExecuteAction(action);
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Cancel the sale and open a new sale
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1   01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickMemberSearch(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (this.FormView.Dirty)
                {
                    if (PivotalMessageBox.Show("Changes to 'Sale:" + this.PrimaryDataRow["Rn_Descriptor"].ToString()
                        + "' will be lost if you exit. Click OK to exit, or Cancel to stay on the current record.", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning)
                        != DialogResult.OK)
                        return;
                }

                this.FormView.CloseForm(false);
                IActionService actionService = ClientContext.ClientAPIService.GetService<IActionService>();
                Command command = Globals.SystemClient.UserProfile.GetMetaItem<Command>("RE.NewSearch.Contact");
                IAction action = actionService.CreateAction(command);
                action.TargetWindow = ActionTargetWindow.Current;
                actionService.ExecuteAction(action);
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Used to display Purchase History depending on Customer-Type
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1   01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickPurchaseHistory(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (string.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Customer_Type"]), "Member"))
                {
                    if (Convert.IsDBNull(this.PrimaryDataRow["Bill_To_Contact_Id"]))
                    {
                        PivotalMessageBox.Show(@"Please select the ""Member"" to check the purchase history.");
                        return;
                    }
                    Globals.ShowSearch("RE_Orders for Bill To Contact ?", new object[] { this.PrimaryDataRow["Bill_To_Contact_Id"] },
                        new string[] { "Bill_To_Contact_Id" }, ActionTargetWindow.Modal);
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Process the deposit transaction.
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   23/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnButtonClickProcessTxn(PivotalControl sender, EventArgs args)
        {
            try
            {
                //DS: 19042013 - For Offline if the POS is not master POS, then don't allow to create new Sale.
                if (SystemClient.SystemInformation.IsMobile && !Globals.IsMasterPOS)
                    PivotalMessageBox.Show("This feature is not available Offline when POS is not Master POS.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                else
                {
                    if (TypeConvert.ToString(this.PrimaryDataRow["RE_Order_Status"]) == "Processed" &&
                        TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Deposit" && TypeConvert.ToString(this.PrimaryDataRow["RE_Deposit_Status"]) == "Pending")
                    {
                        int response = Globals.DialogRadio("", "What would you like to do?", "Convert to Sale", "Cancel Deposit", "Forfeit Deposit");
                        if (response == 0)
                        {
                            //Open a new sale and set the Link Deposit ID in the new sale.
                            TransitionPointParameter transParam = new TransitionPointParameter();
                            ParameterList param = new ParameterList();
                            transParam.Construct();
                            transParam.AddDefaultColumn("RE_Sale_Deposit_Link_Id", this.RecordId);
                            transParam.CopyToParameterList(param);
                            Globals.ShowForm("RE_Sale – Walk In", null, param, ActionTargetWindow.Current);
                        }
                        else if (response == 1 || response == 2)
                        {
                            this.PrimaryDataRow["RE_Deposit_Status"] = (response == 1) ? "Cancel" : "Forfeit";
                            this.SaveRecord();

                            //Send mail to Finance 
                            //DS: 16082013 - New parameters are added to the Deposit Mail.
                            this.SystemClient.ExecuteServerTask("RE_Sale", "SendFinanceEmailForDeposit", new Type[] { typeof(string), typeof(string), typeof(DateTime), 
                                typeof(string) }, new object[] { this.PrimaryDataRow["RE_Receipt_Number"], this.PrimaryDataRow["RE_Deposit_Status"],  
                                TypeConvert.ToDateTime(this.PrimaryDataRow["RE_Order_Date"]), TypeConvert.ToString(this.PrimaryDataRow["Quote_Total"])});

                            Globals.ShowForm("RE_Sale – Walk In", null, null, ActionTargetWindow.Current);
                        }
                    }
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On change of the Quantity field of each cell fo secondary
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void QuantityField_OnDataChange(DataGridViewColumn sender, EventArgs args)
        {
            try
            {
                DataGridView dataGridView = sender.DataGridView;
                DataRow orderProduct = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows[((DataGridViewCellEventArgs)args).RowIndex];
                int originalQuantity = TypeConvert.ToInt32(orderProduct["RE_Source_Qty"]);

                if (Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Receipt_No"]) && (TypeConvert.ToInt32(orderProduct["Quantity"]) < 0))
                {
                    orderProduct["Quantity"] = previousQuantity;
                    CommonFieldPopulate(orderProduct);
                    TotalsSectionCalculations();
                    return;
                }

                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Receipt_No"]) && TypeConvert.ToBoolean(orderProduct["RE_From_Source_Order"]))
                {
                    if (TypeConvert.ToInt32(orderProduct["Quantity"]) < previousQuantity && TypeConvert.ToInt32(orderProduct["Quantity"]) != originalQuantity)
                        orderProduct["Quantity"] = previousQuantity;

                    if (TypeConvert.ToInt32(orderProduct["Quantity"]) >= 0)
                        orderProduct["Quantity"] = previousQuantity;
                    if (!Convert.IsDBNull(orderProduct["RE_Discount_Condition1_Id"]))
                        ApplyDiscount(true, orderProduct);

                    CommonFieldPopulate(orderProduct);
                    TotalsSectionCalculations();
                    return;
                }

                if (previousQuantity > 0 && TypeConvert.ToInt32(orderProduct["Quantity"]) > 0)
                {
                    if (!InventoryCheck(TypeConvert.ToInt32(orderProduct["Quantity"]), true, orderProduct["Product_Id"], orderProduct))
                    {
                        orderProduct["Quantity"] = oldQty;
                        return;
                    }
                }

                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Order_Id"]) && !TypeConvert.ToBoolean(orderProduct["RE_From_Source_Order"]) &&
                    TypeConvert.ToInt32(orderProduct["Quantity"]) <= 0)
                    orderProduct["Quantity"] = previousQuantity;

                if (this.PrimaryDataRow["RE_Source_Order_Id"] != DBNull.Value)
                {
                    QuantityCheck(this.PrimaryDataRow["RE_Source_Order_Id"], orderProduct["Product_Id"], TypeConvert.ToInt32(orderProduct["Quantity"]),
                        orderProduct, ((DataGridViewCellEventArgs)args).RowIndex);

                    CommonFieldPopulate(orderProduct);
                    TotalsSectionCalculations();
                }
                if (popupShown)
                {
                    popupShown = false;
                    return;
                }

                if (TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Refund" && TypeConvert.ToInt32(orderProduct["Quantity"]) >= 0)
                {
                    PivotalMessageBox.Show("Only negative quantities are allowed for Refund transaction.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    orderProduct["Quantity"] = -1;
                    ApplyDiscount(true, orderProduct);
                    CommonFieldPopulate(orderProduct);
                    TotalsSectionCalculations();
                    return;
                }

                //check the quantity against the row where the discount is selected and see if it is less than or equal to the remaining quota.
                //If the quota exceeds the remaining quota, disallow the discount condition and ask the user to change the discount condition or the quantity.
                if (!VerifyQuantityForBdayDisc())
                {
                    //If the quantity exceeds the permissible discount qty, revert the quantity to 1.
                    orderProduct["Quantity"] = 1;
                    orderProduct.AcceptChanges();
                    CommonFieldPopulate(orderProduct);
                    TotalsSectionCalculations();
                    return;
                }

                //Set the value to 1 if user sets it to 0    
                if (TypeConvert.ToInt32(orderProduct["Quantity"]) == 0)
                    orderProduct["Quantity"] = 1;
                else if (TypeConvert.ToInt32(orderProduct["Quantity"]) < 0)
                {
                    EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Discount_Condition1_Id", ((DataGridViewCellEventArgs)args).RowIndex, false);
                    //DS: Only when there is no source order, then make this field non read-only.
                    if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Order_Id"]))
                        EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Staff_Code", ((DataGridViewCellEventArgs)args).RowIndex, false);
                    else
                        EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Staff_Code", ((DataGridViewCellEventArgs)args).RowIndex, true);

                    //if Source Order present, validate against the source order to check if the sku exists in the source order as an item
                    if (this.PrimaryDataRow["RE_Source_Order_Id"] != DBNull.Value)
                    {
                        UpdateExchangeDiscountCondition(Id.Create(this.PrimaryDataRow["RE_Source_Order_Id"]), orderProduct["Product_Id"], 
                            orderProduct, ((DataGridViewCellEventArgs)args).RowIndex);
                        CommonFieldPopulate(orderProduct);
                        TotalsSectionCalculations();
                        return;
                    }
                }

                if (!Convert.IsDBNull(orderProduct["Tier1_Discount_Value"]))
                    orderProduct["Tier1_Discount_Value"] = (TypeConvert.ToDouble(orderProduct["Tier1_Discount_Value"]) / previousQuantity)
                        * TypeConvert.ToInt32(orderProduct["Quantity"]);

                if (TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Exchange" && TypeConvert.ToInt32(orderProduct["Quantity"]) >= 0)
                {
                    orderProduct["RE_Exchange_Reason"] = DBNull.Value;
                    RecalculateAndEnableDisableDisc(((DataGridViewCellEventArgs)args).RowIndex, orderProduct, true);
                }
                else if (TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Exchange" && TypeConvert.ToInt32(orderProduct["Quantity"]) < 0)
                    RecalculateAndEnableDisableDisc(((DataGridViewCellEventArgs)args).RowIndex, orderProduct, false);

                if (TypeConvert.ToInt32(orderProduct["Quantity"]) > 0)
                    EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Staff_Code", ((DataGridViewCellEventArgs)args).RowIndex, true);

                CommonFieldPopulate(orderProduct);
                TotalsSectionCalculations();
                previousQuantity = TypeConvert.ToInt32(orderProduct["Quantity"]);
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// On cell validating event for getting the previous quantity.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        public virtual void Quantity_OnCellValidating(object sender, EventArgs args)
        {
            try
            {
                previousQuantity = TypeConvert.ToInt32(this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"]
                         .Rows[((DataGridViewCellValidatingEventArgs)args).RowIndex]["Quantity"]);
            }
            catch (Exception ex)
            {
                Globals.HandleException(ex, true);
            }
        }

        /// <summary>
        /// On delete of Secondary row
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnSecondaryDeleteClick(PivotalControl sender, EventArgs args)
        {
            try
            {
                DataGridViewCellCancelEventArgs cancelargs = (DataGridViewCellCancelEventArgs)args;
                int rowIndex = cancelargs.RowIndex;
                int appleCareRowIndex = 10000;
                bool deleteAppleCareAfterPrimaryRecord = false;

                DataTable orderProduct = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];

                if (orderProduct.Rows.Count == 1)
                {
                    if (TypeConvert.ToInt32(orderProduct.Rows[rowIndex]["Quantity"]) < 0)
                    {
                        PivotalMessageBox.Show("There should be atleast one item with negative quantity.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                        cancelargs.Cancel = true;
                        return;
                    }
                }

                //If the items added are from Promotion, then do not allow deletion.
                //When the Product is deleted with a Promotion, then delete the associated Products as well.
                if (!Convert.IsDBNull(orderProduct.Rows[rowIndex]["RE_Promo_Ref_Serial"]))
                {
                    //PivotalMessageBox.Show("Promotion items can't be deleted manually. If you wish to delete the promotion, then please delete the Product"
                    //    + " for which promotion is applied.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    cancelargs.Cancel = true;
                    return;
                }
                else if (!Convert.IsDBNull(orderProduct.Rows[rowIndex]["RE_Promotion_Id"]))
                {
                    //If there was a Promotion applied on the Serialized product, then delete the promotion items before deleting the product itself.
                    DataRow[] promotionRows = orderProduct.AsEnumerable().Where(a => TypeConvert.ToString(a["RE_Promo_Ref_Serial"]) ==
                        TypeConvert.ToString(orderProduct.Rows[rowIndex]["RE_Product_Serial_No_Id__Seria"])).ToArray();
                    foreach (DataRow promotionRow in promotionRows)
                    {
                        //NN 19082013: Added code to reset the promotionsCount variable when a Product with promotions is deleted.
                        //NN 15102013: Added addition check for +ve quantity so that deletion of exchange product should not affect the promotionCount.
                        if (TypeConvert.ToString(promotionRow["RE_Product_Type"]) == "Promotion" && TypeConvert.ToInt32(promotionRow["Quantity"]) > 0)
                            promotionsCount = promotionsCount - 1;

                        orderProduct.Rows.Remove(promotionRow);
                    }
                }

                //Added code to delete the record in RE_Authorization if corresponding record in deleted from orderProduct secondary.
                if (TypeConvert.ToBoolean(orderProduct.Rows[rowIndex]["RE_Authorization_Needed_1"]))
                {
                    //Extra Authorization for discounts
                    //Used to fail in case where the DisocuntCondition string contains '%' 
                    //If the string in a LIKE clause contains a * or %, those characters should be enclosed in brackets ([]).
                    DataTable authorzn = this.FormData.DataSet.Tables["RE_Authorization_Order_Id"];
                    string discountCondition = TypeConvert.ToString(orderProduct.Rows[rowIndex]["RE_Discount_Condition1_Id@Rn_Descriptor"]);
                    if (discountCondition.Contains('%') || discountCondition.Contains('*'))
                    {
                        discountCondition = discountCondition.Replace("%", "[%]");
                        discountCondition = discountCondition.Replace("*", "[*]");
                    }
                    DataRow[] authorznRows = authorzn.Select("Event like '" + discountCondition + "'");
                    if (authorznRows != null && authorznRows.Length >= 1)
                        authorzn.Rows.Remove(authorznRows[0]);
                }

                if (Convert.IsDBNull(orderProduct.Rows[rowIndex]["RE_Promo_Ref_Serial"]))
                {
                    //When AppleCareRow is getting deleted
                    if (!Convert.IsDBNull(orderProduct.Rows[rowIndex]["RE_RAE_Serial_Number"]))
                    {
                        DataRow[] primaryProducts = orderProduct.AsEnumerable().Where(a => TypeConvert.ToString(a["RE_Product_Serial_No_Id@Rn_Descriptor"]) ==
                                                    TypeConvert.ToString(orderProduct.Rows[rowIndex]["RE_RAE_Serial_Number"])).ToArray();

                        if (primaryProducts != null && primaryProducts.Length > 0)
                        {
                            if (TypeConvert.ToInt32(primaryProducts[0]["Quantity"]) < 0)
                            {
                                PivotalMessageBox.Show("Cannnot delete this record as it is tagged to a primary product.", MessageBoxButtons.OK, MessageBoxIcon.Information);
                                cancelargs.Cancel = true;
                                return;
                            }
                            else
                            {
                                primaryProducts[0]["RE_AppleCare_Product"] = false;

                                EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_AppleCare_Product", orderProduct.Rows.IndexOf(primaryProducts[0]), true);
                            }
                        }

                        if (!Convert.IsDBNull(orderProduct.Rows[rowIndex]["RE_RAE_Sec_Serial_No"]))
                        {
                            DataRow[] secondaryProducts = orderProduct.AsEnumerable().Where(a => TypeConvert.ToString(a["RE_Product_Serial_No_Id@Rn_Descriptor"]) ==
                                                        TypeConvert.ToString(orderProduct.Rows[rowIndex]["RE_RAE_Sec_Serial_No"])).ToArray();

                            if (secondaryProducts != null && secondaryProducts.Length > 0)
                            {
                                secondaryProducts[0]["RE_AppleCare_Product"] = false;

                                EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_AppleCare_Product", orderProduct.Rows.IndexOf(secondaryProducts[0]), true);
                            }
                        }
                    }
                    else
                    {
                        appleCareRowIndex = AppleCareProductDeletedOrUnchecked(rowIndex);

                        if (appleCareRowIndex != 10000)
                        {
                            if (rowIndex > appleCareRowIndex)
                                deleteAppleCareAfterPrimaryRecord = true;
                            else
                            {
                                orderProduct.Rows.Remove(orderProduct.Rows[appleCareRowIndex]);
                            }

                        }
                    }
                }

                orderProduct.Rows.Remove(orderProduct.Rows[rowIndex]);
                if(deleteAppleCareAfterPrimaryRecord)
                    orderProduct.Rows.Remove(orderProduct.Rows[appleCareRowIndex]);


                TotalsSectionCalculations();

                //Post deletion if there are no records in the secondary, then enable the Customer_Type and the other fields.
                if (this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count == 0)
                    Globals.EnableDisablePrimaryFields(true, new string[] { "RE_Customer_Type", "RE_Customer_Id", "Bill_To_Contact_Id" });
                cancelargs.Cancel = true;
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On exit of StaffCode of Secondary row
        /// </summary>
        /// <param name="sender">object</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void StaffCode_OnCellExit(object sender, EventArgs args)
        {
            try
            {
                DataGridViewCellEventArgs evntArgs = (DataGridViewCellEventArgs)args;
                DataTable orderProduct = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];

                if (!Convert.IsDBNull(orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Code"]))
                {
                    DataTable staff = Globals.GetDataTable("RE_Active Staff with Staff Code?",
                        new object[] { orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Code"] }, "RE_Staff_Id");

                    if (staff != null && staff.Rows.Count == 1)
                    {
                        orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Id"] = staff.Rows[0]["RE_Staff_Id"];
                        return;
                    }
                    else if (staff != null && staff.Rows.Count > 1)
                        PivotalMessageBox.Show("Multiple Staff records are found for the code entered: " + orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Code"]
                            + Environment.NewLine + "Please contact the Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                    else
                        PivotalMessageBox.Show("No Staff record found for the keyed in Sales Rep Code: " + orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Code"]
                            , MessageBoxButtons.OK, MessageBoxIcon.Warning);

                    orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Code"] = DBNull.Value;
                    orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Id"] = DBNull.Value;
                }
                else
                    orderProduct.Rows[evntArgs.RowIndex]["RE_Staff_Id"] = DBNull.Value;
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// On change of Sale Rep Code field on enter key hit or tab out
        /// </summary>
        /// <param name="sender">PivotalControl</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void SalesRepCode_DataSourceUpdated(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Staff_Code"]))
                {
                    DataTable staff = Globals.GetDataTable("RE_Active Staff with Staff Code?", new object[] { this.PrimaryDataRow["RE_Staff_Code"] }, "RE_Staff_Id");

                    if (staff != null && staff.Rows.Count == 1)
                    {
                        this.PrimaryDataRow["RE_Staff_Id"] = staff.Rows[0]["RE_Staff_Id"];

                        foreach (DataRow dr in this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows)
                        {
                            if (TypeConvert.ToInt32(dr["Quantity"]) > 0)
                            {
                                dr["RE_Staff_Id"] = this.PrimaryDataRow["RE_Staff_Id"];
                                dr["RE_Staff_Code"] = this.PrimaryDataRow["RE_Staff_Code"];
                            }
                            else if (Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Receipt_No"]))
                            {
                                dr["RE_Staff_Id"] = this.PrimaryDataRow["RE_Staff_Id"];
                                dr["RE_Staff_Code"] = this.PrimaryDataRow["RE_Staff_Code"];
                            }
                        }
                        return;
                    }
                    else if (staff != null && staff.Rows.Count > 1)
                        PivotalMessageBox.Show("Multiple Staff records are found for the code entered. Please contact the Administrator.", MessageBoxButtons.OK, MessageBoxIcon.Stop);
                    else
                        PivotalMessageBox.Show("No Staff record found for the keyed in Sales Rep Code.", MessageBoxButtons.OK, MessageBoxIcon.Warning);

                    this.PrimaryDataRow["RE_Staff_Code"] = DBNull.Value;
                    this.PrimaryDataRow["RE_Staff_Id"] = DBNull.Value;
                }
                else
                    this.PrimaryDataRow["RE_Staff_Id"] = DBNull.Value;

                this.FormControl.GetControlByDataName("RE_Staff_Code").Focus();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On change of Product field 
        /// </summary>
        /// <param name="sender">PivotalControl</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnDataSourceUpdatedProduct(PivotalControl sender, EventArgs args)
        {
            try
            {
                bool productAdded = false;
                if (this.PrimaryDataRow["RE_Product_Id"] != DBNull.Value)
                {
                    DataTable product = Globals.GetDataTable("Product", new List<NameValuePair>() { new NameValuePair("Product_Id", this.PrimaryDataRow["RE_Product_Id"]) });
                    if (String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Refund"))
                        PivotalMessageBox.Show("Products can't be added in a refund case." + Environment.NewLine +
                        "Please scan/enter the Source Receipt and delete the items not required to be refunded and proceed.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    else if (Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Order_Id"]) && String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Exchange"))
                        PivotalMessageBox.Show("Please scan/enter the Source Receipt before adding any product for Exchange.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    else if (InventoryCheck(1, false, product.Rows[0]["Product_Id"], null))
                    {
                        //Check whether it is a serialized item or not.
                        if (!TypeConvert.ToBoolean(product.Rows[0]["RE_Serialized"]))
                        {
                            //Non-Serialized Item. Add the product directly to the grid.
                            if (AddProductToGrid(product, null))
                                productAdded = true;
                        }
                        else
                        {
                            ((PivotalForeignKey)this.FormControl.GetControlByDataName("RE_Product_Serial_No_Id")).ReadOnly = false;
                            ((PivotalTextBox)this.FormControl.GetControlByDataName("RE_Serial_Number")).ReadOnly = false;
                            this.FormControl.GetControlByDataName("RE_Serial_Number").Focus();
                            return;
                        }
                    }
                }
                this.PrimaryDataRow["RE_Product_Id"] = DBNull.Value;
                this.PrimaryDataRow["RE_Serial_Number"] = DBNull.Value;
                this.PrimaryDataRow["RE_Product_Serial_No_Id"] = DBNull.Value;
                ((PivotalTextBox)this.FormControl.GetControlByDataName("RE_Serial_Number")).ReadOnly = true;
                ((PivotalForeignKey)this.FormControl.GetControlByDataName("RE_Product_Serial_No_Id")).ReadOnly = true;
                //DS: 12052013 - When the promotion product is scanned, the focus should be set properly. scannedPromotionProduct check added.
                if (productAdded || scannedPromotionProduct)
                    this.FormControl.GetControlByName("REProductBarcode").Focus();
                else if (String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Refund") ||
                    (Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Order_Id"]) && String.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]), "Exchange")))
                    this.FormControl.GetControlByDataName("RE_Source_Receipt_No").Focus();
                else
                    this.FormControl.GetControlByDataName("RE_Product_Id").Focus();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On change of Membership/Scan Id field on enter key hit or tab out
        /// </summary>
        /// <param name="sender">PivotalControl</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0   28/01/2013  DS      Initial Version
        /// </history>
        public virtual void OnDataSourceUpdatedMembershipID(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (this.PrimaryDataRow["RE_Customer_Id"] != DBNull.Value)
                {
                    if (TypeConvert.ToBoolean(this.PrimaryDataRow["IC_Validate_For_VIP"]))
                    {
                        //Query with both Membership Id and IC Number with a or condition.
                        DataTable memberWithICValidate = Globals.GetDataTable("RE_Members with Membership ID? or Identification Number?",
                            new object[] { this.PrimaryDataRow["RE_Customer_Id"], this.PrimaryDataRow["RE_Customer_Id"] }, "Contact_Id", "RE_Status");

                        if (memberWithICValidate != null && memberWithICValidate.Rows.Count == 1)
                        {
                            //DS: Check if the Member Status is Expired. If so, then prompt the user that the Membership Status is Expired.
                            if (TypeConvert.ToString(memberWithICValidate.Rows[0]["RE_Status"]) == "Expired")
                            {
                                PivotalMessageBox.Show("Membership status for the member: " + TypeConvert.ToString(this.PrimaryDataRow["RE_Customer_Id"]) + " is Expired.",
                                    MessageBoxButtons.OK, MessageBoxIcon.Information);
                                this.PrimaryDataRow["RE_Customer_Id"] = DBNull.Value;
                                this.FormControl.GetControlByDataName("RE_Customer_Id").Focus();
                                return;
                            }
                            else
                            {
                                this.PrimaryDataRow["Bill_To_Contact_Id"] = memberWithICValidate.Rows[0]["Contact_Id"];
                                this.PrimaryDataRow["RE_Customer_Type"] = "Member";
                                EnableDisableRemainingQuota();

                                if (this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count > 0)
                                {
                                    //Recalculate the discount conditions and other params.
                                    UpdateOrderProductGrid("M");
                                    Globals.EnableDisablePrimaryFields(false, new string[] { "RE_Customer_Type", "RE_Customer_Id", "Bill_To_Contact_Id" });
                                }
                                return;
                            }
                        }
                        else if (memberWithICValidate != null && memberWithICValidate.Rows.Count > 1)
                        {
                            PivotalMessageBox.Show("Multiple Members are found for the ID provided. Please contact system Administrator.", MessageBoxButtons.OK,
                                MessageBoxIcon.Error);
                            this.PrimaryDataRow["RE_Customer_Id"] = DBNull.Value;
                            this.FormControl.GetControlByDataName("RE_Customer_Id").Focus();
                            return;
                        }
                    }
                    else
                    {
                        DataTable memberWithoutICValidate = Globals.GetDataTable("RE_Members with Membership ID?",
                            new object[] { this.PrimaryDataRow["RE_Customer_Id"] }, "Contact_Id", "RE_Status");

                        if (memberWithoutICValidate != null && memberWithoutICValidate.Rows.Count == 1)
                        {
                            if (TypeConvert.ToString(memberWithoutICValidate.Rows[0]["RE_Status"]) == "Expired")
                            {
                                PivotalMessageBox.Show("Membership status for the Member: " + TypeConvert.ToString(this.PrimaryDataRow["RE_Customer_Id"]) + " is Expired.",
                                    MessageBoxButtons.OK, MessageBoxIcon.Information);
                                this.PrimaryDataRow["RE_Customer_Id"] = DBNull.Value;
                                this.FormControl.GetControlByDataName("RE_Customer_Id").Focus();
                                return;
                            }
                            else
                            {
                                this.PrimaryDataRow["Bill_To_Contact_Id"] = memberWithoutICValidate.Rows[0]["Contact_Id"];
                                this.PrimaryDataRow["RE_Customer_Type"] = "Member";
                                EnableDisableRemainingQuota();

                                if (this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows.Count > 0)
                                {
                                    //Recalculate the discount conditions and other params.
                                    UpdateOrderProductGrid("M");
                                    Globals.EnableDisablePrimaryFields(false, new string[] { "RE_Customer_Type", "RE_Customer_Id", "Bill_To_Contact_Id" });
                                }
                                return;
                            }
                        }
                        else if (memberWithoutICValidate != null && memberWithoutICValidate.Rows.Count > 1)
                        {
                            PivotalMessageBox.Show("Multiple Members are found for the ID provided. Please contact the System Administrator.",
                                MessageBoxButtons.OK,
                                MessageBoxIcon.Error);
                            this.PrimaryDataRow["RE_Customer_Id"] = DBNull.Value;
                            this.FormControl.GetControlByDataName("RE_Customer_Id").Focus();
                            return;
                        }
                    }
                    PivotalMessageBox.Show("No Member found for the scanned Membership ID.",
                            MessageBoxButtons.OK, MessageBoxIcon.Error);

                    this.PrimaryDataRow["RE_Customer_Id"] = DBNull.Value;
                    this.FormControl.GetControlByDataName("RE_Customer_Id").Focus();
                }
                else
                {
                    this.PrimaryDataRow["Bill_To_Contact_Id"] = DBNull.Value;
                    this.PrimaryDataRow["RE_Customer_Type"] = "Walk-In";
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// SourceReceiptNo keyed in or populated after being scanned
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.0    06/11/2012  DS      Initial Version
        /// </history>
        public virtual void OnKeyDownSourceReceiptNo(PivotalControl sender, KeyEventArgs args)
        {
            try
            {
                //If Enter key is hit
                if (args.KeyCode == Keys.Enter)
                {
                    this.FormControl.GetControlByDataName("RE_Receipt_Number").Focus();//This is necessary to fire the datasource updated event.
                    this.FormControl.GetControlByDataName("RE_Source_Receipt_No").Focus();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// On exit of Source Receipt No. field 
        /// </summary>
        /// <param name="sender">PivotalControl</param>
        /// <param name="args">EventArgs</param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1   01/02/2013  DS      Initial Version
        /// </history>
        public virtual void OnDataSourceUpdatedSourceReceiptNo(PivotalControl sender, EventArgs args)
        {
            try
            {
                DataTable orderProducts = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                if (!Convert.IsDBNull(this.PrimaryDataRow["RE_Source_Receipt_No"]))
                {
                    DataTable sourceOrder = Globals.GetDataTable("RE_Orders with Order Status Processed and Receipt No ?",
                        new object[] { TypeConvert.ToString(this.PrimaryDataRow["RE_Source_Receipt_No"]) },
                        "RE_Source_Order_Id", "SFA_Order_Id", "RE_Customer_Type", "Bill_To_Contact_Id", "RE_Customer_Id", "RE_Order_Date","RE_External_Transaction_No");

                    if (sourceOrder != null && sourceOrder.Rows.Count == 1)
                    {
                        //Check if this receipt is used already in another refund transaction which is processed.
                        DataTable refundOrdersWithSourceOrder = Globals.GetDataTable("RE_Processed Refund transaction with Source Order?",
                            new object[] { sourceOrder.Rows[0]["SFA_Order_Id"] }, "SFA_Order_Id");
                        if (refundOrdersWithSourceOrder != null && refundOrdersWithSourceOrder.Rows.Count > 0)
                        {
                            this.PrimaryDataRow["RE_Source_Receipt_No"] = DBNull.Value;
                            PivotalMessageBox.Show("Source receipt is already used in another Refund transaction.", MessageBoxButtons.OK, MessageBoxIcon.Asterisk);
                        }
                        else
                        {
                            //Fetch the Exchnage/Refund allowed days for the order from the LOB.
                            double exchangeRefundDays = TypeConvert.ToDouble(Globals.SqlIndex("RE_Line_Of_Business", "Exchange_Refund_Days", Id.Create(this.PrimaryDataRow["RE_LOB_Id"])));
                            if (TypeConvert.ToDateTime(sourceOrder.Rows[0]["RE_Order_Date"]).Date.AddDays(exchangeRefundDays) >= DateTime.Now.Date)
                            {
                                //set the source order with the sfa_order_id retrieved
                                this.PrimaryDataRow["RE_Source_Order_Id"] = sourceOrder.Rows[0]["SFA_Order_Id"];
                                this.PrimaryDataRow["RE_Customer_Type"] = sourceOrder.Rows[0]["RE_Customer_Type"];

                                if (string.Equals(TypeConvert.ToString(this.PrimaryDataRow["RE_Customer_Type"]), "Member"))
                                {
                                    //Set all the Member Info.
                                    this.PrimaryDataRow["RE_Customer_Id"] = sourceOrder.Rows[0]["RE_Customer_Id"];
                                    OnDataSourceUpdatedMembershipID(sender, args);
                                }

                                //Disabling RE_Source_Receipt_No when a valid RE_Source_Receipt_No is set for the first time.
                                Globals.EnableDisablePrimaryFields(false, "RE_Source_Receipt_No");

                                DataTable order_Products = Globals.GetDataTable("RE_Order Products with Status as Processed and Type as Non refund with Order ?",
                                    new object[] { this.PrimaryDataRow["RE_Source_Order_Id"] }, new string[] { });

                                if (order_Products != null && order_Products.Rows.Count > 0)
                                {
                                    for (int i = orderProducts.Rows.Count - 1; i >= 0; i--)
                                    {
                                        orderProducts.Rows[i].Delete();
                                    }
                                    foreach (DataRow drTemp in order_Products.Rows)
                                    {
                                        //DS: 20052013 - Promotion items also should be added from the Source Order. For the Promotion product line item, -ve qty should be allowed.
                                        if ((TypeConvert.ToInt32(drTemp["Quantity"]) > 0 && !TypeConvert.ToBoolean(drTemp["RE_Invisible"])) ||
                                            (TypeConvert.ToInt32(drTemp["Quantity"]) < 0 && string.Equals(TypeConvert.ToString(drTemp["RE_Product_Type"]).ToUpper(), "PROMOTION")))
                                        {
                                            base.NewSecondaryRecord("SFA_Order__Product_SFA_Order_I");
                                            DataRow orderProduct = orderProducts.Rows[orderProducts.Rows.Count - 1];
                                            orderProduct["Product_Id"] = drTemp["Product_Id"];
                                            orderProduct["RE_Product_Type"] = drTemp["RE_Product_Type"];
                                            orderProduct["RE_Staff_Code"] = drTemp["RE_Staff_Code"];
                                            orderProduct["Unit_Price"] = drTemp["Unit_Price"];
                                            orderProduct["RE_Storage_Location_Id"] = drTemp["RE_Storage_Location_Id"];
                                            orderProduct["RE_Invisible"] = drTemp["RE_Invisible"];
                                            orderProduct["RE_Staff_Id"] = drTemp["RE_Staff_Id"];
                                            orderProduct["Quantity"] = -TypeConvert.ToInt32(drTemp["Quantity"]);
                                            //NN 5 Apr 2013:
                                            //Added code for NetPrice calculation when Source Order is from Airport Counters and TaxAmount = 0
                                            if (sourceOrder.Rows[0]["RE_External_Transaction_No"] != DBNull.Value &&
                                                TypeConvert.ToDouble(drTemp["Tax_Amount"]) == 0)
                                            {
                                                orderProduct["RE_Extended_Price"] = -this.SetPriceForExchangeRefundFromAirportCounter(drTemp);
                                            }
                                            else
                                                orderProduct["RE_Extended_Price"] = -TypeConvert.ToDouble(drTemp["RE_Extended_Price"]);
                                            //DS: 14062013 - Exchange/Refund reason must be entered manually. Points are not being used.
                                            //orderProduct["RE_Exchange_Reason"] = drTemp["RE_Exchange_Reason"];
                                            //orderProduct["RE_Refund_Reason"] = drTemp["RE_Refund_Reason"];
                                            //orderProduct["RE_Points"] = drTemp["RE_Points"];
                                            orderProduct["RE_Profit"] = -TypeConvert.ToDouble(drTemp["RE_Profit"]);
                                            orderProduct["RE_Revenue"] = -TypeConvert.ToDouble(drTemp["RE_Revenue"]);
                                            orderProduct["RE_Unit_Cost_Price"] = -TypeConvert.ToDouble(drTemp["RE_Unit_Cost_Price"]);
                                            //DS: 14062013 - Void Order can not be Exchanged/Refunded.
                                            //orderProduct["RE_Void"] = drTemp["RE_Void"];
                                            orderProduct["Tax_Amount"] = -TypeConvert.ToDouble(drTemp["Tax_Amount"]);
                                            orderProduct["Tax_Percentage"] = drTemp["Tax_Percentage"];
                                            //DS: 14062013 - Order Id must not be set as this should be done by Platform. Removing duplicates
                                            //orderProduct["SFA_Order_Id"] = drTemp["SFA_Order_Id"];
                                            //orderProduct["RE_Invisible"] = drTemp["RE_Invisible"];
                                            //orderProduct["RE_Product_Type"] = drTemp["RE_Product_Type"];
                                            orderProduct["RE_Exclude_In_Net_Sales"] = drTemp["RE_Exclude_In_Net_Sales"];
                                            orderProduct["RE_From_Source_Order"] = true;
                                            orderProduct["RE_Source_Qty"] = orderProduct["Quantity"];
                                            orderProduct["RE_Product_Serial_No_Id"] = drTemp["RE_Product_Serial_No_Id"];
                                            orderProduct["RE_Comments"] = drTemp["RE_Comments"];
                                            orderProduct["RE_Promotion_Id"] = drTemp["RE_Promotion_Id"];
                                            orderProduct["RE_Mandatory_Promotion"] = drTemp["RE_Mandatory_Promotion"];
                                            orderProduct["RE_Promo_Ref_Serial"] = drTemp["RE_Promo_Ref_Serial"];
                                            orderProduct["RE_Item_Scanned"] = true;
                                            orderProduct["RE_Discount_Condition1_Id"] = drTemp["RE_Discount_Condition1_Id"];
                                            orderProduct["Tier1_Discount_Value"] = drTemp["Tier1_Discount_Value"];
                                            orderProduct["Tier1_Discount_Percent"] = drTemp["Tier1_Discount_Percent"];
                                            orderProduct["RE_Authorization_Needed_1"] = drTemp["RE_Authorization_Needed_1"];
                                            orderProduct["RE_Voucher_Number"] = drTemp["RE_Voucher_Number"];

                                            //NN 11062013:
                                            //Added code to copy Original_PO_Number for Apple Care implementation
                                            orderProduct["RE_Original_PO_Number"] = drTemp["RE_PO_Number"];
                                            orderProduct["RE_RAE_Serial_Number"] = drTemp["RE_RAE_Serial_Number"];
                                            orderProduct["RE_RAE_Sec_Serial_No"] = drTemp["RE_RAE_Sec_Serial_No"];
                                            orderProduct["RE_AppleCare_Product"] = drTemp["RE_AppleCare_Product"];
                                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_AppleCare_Product", orderProducts.Rows.Count - 1, false);

                                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Staff_Code", orderProducts.Rows.Count - 1, false);
                                            EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Discount_Condition1_Id", orderProducts.Rows.Count - 1, false);
                                        }
                                    }
                                }
                            }
                            else
                            {
                                PivotalMessageBox.Show("Exchange/Refund can only be done within " + exchangeRefundDays + " days of purchase.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                this.PrimaryDataRow["RE_Source_Receipt_No"] = DBNull.Value;
                                this.PrimaryDataRow["RE_Source_Order_Id"] = DBNull.Value;
                                this.FormControl.GetControlByDataName("RE_Source_Receipt_No").Focus();
                            }
                        }
                    }
                    else
                    {
                        PivotalMessageBox.Show("Invalid Receipt Number. Please try again.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        this.PrimaryDataRow["RE_Source_Receipt_No"] = DBNull.Value;
                        this.PrimaryDataRow["RE_Source_Order_Id"] = DBNull.Value;
                        this.FormControl.GetControlByDataName("RE_Source_Receipt_No").Focus();
                    }
                }
                else
                {
                    this.PrimaryDataRow["RE_Source_Order_Id"] = DBNull.Value;
                    if (orderProducts.Rows.Count > 0)
                    {
                        foreach (DataRow orderProduct in orderProducts.Rows)
                        {
                            if (TypeConvert.ToString(this.PrimaryDataRow["RE_Type"]) == "Exchange" && TypeConvert.ToInt32(orderProduct["Quantity"]) >= 0)
                                orderProduct["RE_Exchange_Reason"] = DBNull.Value;

                            CommonFieldPopulate(orderProduct);
                        }
                    }
                }

                TotalsSectionCalculations();
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Collect the Discount conditions descriptor before it changes.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1   08/04/2013  DS      Initial Version
        /// </history>
        public void OnCellValidatingDiscCondition1(object sender, EventArgs args)
        {
            try
            {
                previousDiscCondDesc = TypeConvert.ToString(this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].DefaultView.ToTable()
                    .Rows[((DataGridViewCellEventArgs)args).RowIndex]["RE_Discount_Condition1_Id__Rn_"]);
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// Calculate amount/percent on the basis of Discount Condition 2 selected
        /// </summary>
        /// <history>
        /// Revision   Date        Author  Description
        /// 6.0.12.1   08/04/2013  DS      Initial Version
        /// </history>
        public void OnDataSourceUpdatedDiscCondition1(object sender, EventArgs args)
        {
            try
            {
                DataRow orderProduct = this.FormData.DataSet.Tables["SFA_Order__Product_SFA_Order_I"].Rows[((DataGridViewCellEventArgs)args).RowIndex];

                if (!Convert.IsDBNull(orderProduct["RE_Discount_Condition1_Id"]))
                {
                    //Will be used to set focus to other field so that next time the previousDiscCondDesc value(CellEnter event) is set correctly.
                    //This value is used while deleting the Authorization record in case of change/removal of the discountcondition
                    SetFocusOnSecondaryCell((DataGridViewColumn)sender, args);
                }
                //Check if Bday Discount condition is selected. If so, check if the Bday is in the current month or not. Otherwise do not allow the user to select this.
                if (orderProduct["RE_Discount_Condition1_Id"] != DBNull.Value && this.PrimaryDataRow["Member_Bday_Discount_Id"] != DBNull.Value &&
                    Id.Create(orderProduct["RE_Discount_Condition1_Id"]) == Id.Create(this.PrimaryDataRow["Member_Bday_Discount_Id"]))
                {
                    //BR: Fix of Issue #24 
                    if (TypeConvert.ToString(this.PrimaryDataRow["RE_Customer_Type"]) == "Member")
                    {
                        if (this.PrimaryDataRow["Birthday"] != DBNull.Value && (TypeConvert.ToDateTime(this.PrimaryDataRow["Birthday"]).Month != DateTime.Now.Month))
                        {
                            PivotalMessageBox.Show("Birthday discount can only be applied in the Member's Birthday Month.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            orderProduct["RE_Discount_Condition1_Id"] = DBNull.Value;
                            return;
                        }
                        else
                        {
                            //Check for Birthday_Promotion,Bday_Promo_Quota,Member_Bday_Discount_Id. Show the field Bday_Remaining_Quota.
                            if (!TypeConvert.ToBoolean(this.PrimaryDataRow["Birthday_Promotion"]))
                            {
                                PivotalMessageBox.Show("Birthday discount can only be applied when the Loyalty Program Tier participates in the Birthday promotion.",
                                    MessageBoxButtons.OK, MessageBoxIcon.Error);
                                orderProduct["RE_Discount_Condition1_Id"] = DBNull.Value;
                                return;
                            }
                            else
                            {
                                //check the quantity against the row where the discount is selected and see if it is less than or equal to the remaining quota.
                                //If the quota exceeds the remaining quota, disallow the discount condition and ask the user to change the discount condition or the quantity.
                                if (!VerifyQuantityForBdayDisc())
                                {
                                    orderProduct["RE_Discount_Condition1_Id"] = DBNull.Value;
                                    return;
                                }
                            }
                        }
                    }
                    else
                    {
                        PivotalMessageBox.Show("The selected discount is of type Birthday discount and can only be applied for Members in their Birthday month.",
                            MessageBoxButtons.OK, MessageBoxIcon.Error);
                        orderProduct["RE_Discount_Condition1_Id"] = DBNull.Value;
                        return;
                    }
                }

                //No Top Management case.
                ////BR: Code start Top Management
                //if (!Convert.IsDBNull(orderProduct["RE_Discount_Condition1_Id"]) && !Convert.IsDBNull(this.PrimaryDataRow["RE_Top_Management_Id"]))
                //{
                //    //Validate to check if that discount condition is present in 
                //    //the RE_Staff_Purchase_Prof_Quota records for the Staff Purchase Profile for the Staff Id selected in the Top Management field.
                //    DataTable topStaff = Globals.GetDataTable("RE_Staff Purchase Profile Quota for Staff ? LOB ?",
                //        new object[] { this.PrimaryDataRow["RE_Top_Management_Id"], this.PrimaryDataRow["RE_LOB_Id"] }, "Discount_Condition_Id");

                //    if (topStaff != null && topStaff.Rows.Count > 0)
                //    {
                //        //If Disc. Condition is present/matches allow the condition to be selected on the grid else not.
                //        if (topStaff.AsEnumerable().Count(a => a["Discount_Condition_Id"] != DBNull.Value) == 0
                //            || topStaff.AsEnumerable().Where(a => Id.Create(a["Discount_Condition_Id"]) != Id.Create(orderProduct["RE_Discount_Condition1_Id"]))
                //            .Count() == topStaff.Rows.Count)
                //        {
                //            {
                //                PivotalMessageBox.Show("Discount Condition applied does not match the discount condition in Staff Purchase Profile Quota. " +
                //                    "Please choose another condition.", MessageBoxButtons.OK, MessageBoxIcon.Error);
                //                //do not let the discount grid be selected
                //                orderProduct["RE_Discount_Condition1_Id"] = DBNull.Value;
                //                return;
                //            }
                //        }
                //    }
                //}

                //Apply the appropriate discount.
                ApplyDiscount(true, orderProduct);

                CommonFieldPopulate(orderProduct);
                TotalsSectionCalculations();

                //No such condition where discount condition can be a voucher.
                ////NN 26 March 2012:Issue 72
                ////Added code to enable RE_Voucher_Number only if RE_Discount_Condition1_Id__Vou is checked.
                //if (TypeConvert.ToBoolean(orderProduct["RE_Discount_Condition1_Id__Vou"]))
                //{
                //    EnableDisableDataGridCell("SFA_Order__Product_SFA_Order_I", "RE_Voucher_Number", ((DataGridViewCellEventArgs)args).RowIndex, true);
                //}
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc);
            }
        }

        /// <summary>
        /// Will be called when "Add Apple Care" checkbox is clicked.
        /// Will be used to scan through existing Secondary records for finding matching Product as = RAE_Secondary_AC_Product.Secondary_AC_product_Id
        /// If not found will create a new record in OrderProduct secondary with 
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        public void OnCellValueChangedAppleCareProduct(object sender, EventArgs args)
        {
            try
            {
                bool canAddNewRowForSerailNumber = false;
                DataTable orderProducts = this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];
                //Current record
                DataRow orderProduct = orderProducts.Rows[((DataGridViewCellEventArgs)args).RowIndex];

                if (TypeConvert.ToBoolean(orderProduct["RE_AppleCare_Product"]))
                {
                    Id appleCareProductId = Id.Create(orderProduct["Product_Id__RE_Apple_Care_Prod"]);

                    //Fetching all the AppleCareProductrecords with RE_RAE_Sec_Serial_No = NULL.
                    //So that we can validate such rows for secondary Warranty
                    DataRow[] appleCareProducts = orderProducts.AsEnumerable().Where(a => a["RE_RAE_Serial_Number"] != DBNull.Value && Convert.IsDBNull(a["RE_RAE_Sec_Serial_No"])).ToArray();

                    if (appleCareProducts != null && appleCareProducts.Length > 0)
                    {
                        //Fetching records from RAE_Secondary_AC_Product where current Product is defined as Secondary_AC_Product
                        DataTable raeSeconddaryACProducts = Globals.GetDataTable("RE_Secondary_Products with Secondary Product ?", new object[] { orderProduct["Product_Id"] },
                                                                                new string[] { "Primary_AC_Product_Id" });

                        if (raeSeconddaryACProducts != null && raeSeconddaryACProducts.Rows.Count > 0)
                        {
                            //Looping through all the Primary_AC_Products to find if Apple Care is already applied for this product in the current 
                            //Product secondary grid.
                            foreach (DataRow drRaeSeconddaryACProduct in raeSeconddaryACProducts.Rows)
                            {                                
                                var productswithAppleCareApplicable = (from DataRow dr1 in orderProducts.Rows
                                                                       where Id.Create(dr1["Product_Id"]) == Id.Create(drRaeSeconddaryACProduct["Primary_AC_Product_Id"])
                                                                       select new
                                                                        {
                                                                            col1 = TypeConvert.ToString(dr1["RE_Product_Serial_No_Id@Rn_Descriptor"])
                                                                        });


                                var appleCareProductsAlreadyAdded = (from DataRow dr2 in appleCareProducts
                                                                     select new
                                                                        {
                                                                            col1 = TypeConvert.ToString(dr2["RE_RAE_Serial_Number"])
                                                                        });

                                var intersect = appleCareProductsAlreadyAdded.Intersect(productswithAppleCareApplicable);

                                if (intersect != null && intersect.Count() > 0)
                                {
                                    foreach (var i in intersect)
                                    {
                                        DataRow[] appleCareRecordsToBeModified = appleCareProducts.AsEnumerable().Where(a => TypeConvert.ToString(a["RE_RAE_Serial_Number"]) == TypeConvert.ToString(i.col1)).ToArray();
                                        if (appleCareRecordsToBeModified != null && appleCareRecordsToBeModified.Length > 0)
                                        {
                                            canAddNewRowForSerailNumber = false;
                                            appleCareRecordsToBeModified[0]["RE_RAE_Sec_Serial_No"] = orderProduct["RE_Product_Serial_No_Id@Rn_Descriptor"];
                                            return;
                                        }
                                        break;
                                    }
                                }
                                else                                     
                                    canAddNewRowForSerailNumber = true;     
                            }
                            if (canAddNewRowForSerailNumber)
                                this.AddAppleCareProductToGrid(appleCareProductId, TypeConvert.ToString(orderProduct["RE_Product_Serial_No_Id@Rn_Descriptor"]), "C");       
                        }
                        else
                            this.AddAppleCareProductToGrid(appleCareProductId,TypeConvert.ToString(orderProduct["RE_Product_Serial_No_Id@Rn_Descriptor"]), "C");
                    }
                    else
                        this.AddAppleCareProductToGrid(appleCareProductId, TypeConvert.ToString(orderProduct["RE_Product_Serial_No_Id@Rn_Descriptor"]), "C");
                }
                else
                {
                    int appleCareRowIndex = this.AppleCareProductDeletedOrUnchecked(((DataGridViewCellEventArgs)args).RowIndex);

                    if (appleCareRowIndex != 10000)                        
                        orderProducts.Rows.Remove(orderProducts.Rows[appleCareRowIndex]);

                    TotalsSectionCalculations();
                }
            }
            catch(Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        /// <history>
        /// 
        /// </history>
        public void OnButtonClickAddInstallBase(PivotalControl sender, EventArgs args)
        {
            try
            {
                if (this.FormView.Dirty)
                {
                    if (!this.SaveRecord())
                        return;

                    this.LoadRecord();
                }

                TransitionPointParameter tpp = new TransitionPointParameter();                
                tpp.SetUserDefinedParameter(1, this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"]);
                Globals.NewForm("RE_AddInstallBaseItem",tpp.ParameterList , ActionTargetWindow.Modal);

                if (Globals.AddInstallBase != null)
                {
                    Id AppleProductId = Id.Create(Globals.AddInstallBase[0]);
                    string serialNo = TypeConvert.ToString(Globals.AddInstallBase[1]);

                    DataTable orderProducts = this.DataSet.Tables["SFA_Order__Product_SFA_Order_I"];

                    DataRow[] primaryProduct = orderProducts.AsEnumerable().Where(a => TypeConvert.ToString(a["RE_Product_Serial_No_Id@Rn_Descriptor"]) == serialNo).ToArray();

                    if (primaryProduct != null && primaryProduct.Length > 0)
                    {
                        primaryProduct[0]["RE_AppleCare_Product"] = true;
                    }
                    this.OnFormReloaded();
                    this.AddAppleCareProductToGrid(AppleProductId, serialNo, "I");

                    Globals.AddInstallBase = null;
                }
                else
                {
                    this.OnFormReloaded();
                }
            }
            catch (Exception exc)
            {
                Globals.HandleException(exc, true);
            }
        }
    }
}


